using namespace std;
#pragma once
#include <iostream>
#include <vector>
#include <semaphore.h>
#include <unistd.h>
#include <pthread.h>
//对sem_t常用接口的封装
namespace SemModule
{
    int defaultsemval = 1;
    class Sem
    {
    public:
    //sem_t的构造函数就是sem_t生成对象的初始化
    //就是对sem_init函数的封装,此函数的第一参数和第二参数不用user多考虑
    //需要主动初始化的是第三参数,因为第三参数有好几种常见不同情况,对于剩余可存储的信号以及当前持有信号
        Sem(int value = defaultsemval)//缺省参数
        : _init_vaule(value)//自定义参数 初始化大小 当前存信号量初始化为0 还可存储信号量为cap
        {
            int n = sem_init(&_sem, 0, _init_vaule);
            (void)n; // 对返回值不作判断
        }

        void P()//等待信号量减少
        {
            int m=sem_wait(&_sem);
        }
        void V()//增加信号量
        {
            int n=sem_post(&_sem);
        }
        ~Sem(){int m = sem_destroy(&_sem);}

    private:
        sem_t _sem;
        int _init_vaule;
    };
}

//有关构造函数的参数列表和初始化列表
//相同点就是二者都是对成员变量进行初始化
//不同点是参数列表一般是需要user主动传参的,或者是某个成员变量需要user手动传参且共享同一参数
//初始化列表则一般接受来自参数列表变量的初始化或者user既定的默认值
//且user使用此类类型进行对象创建时只能对其构造函数的参数列表中的成员变量进行初始化
//构造函数体内一般是某个成员变量初始化需要其他函数对其进行初始化的变量的初始化区域

//=============================================================================================

namespace SemModule
{
    int defaultsemval = 1;
    class Sem
    {
    public:
        Sem(int value = defaultsemval)
        : _init_vaule(value)
        {
            int n = sem_init(&_sem, 0, _init_vaule);
            (void)n; 
        }
        void P() {int m=sem_wait(&_sem);}
        void V() {int n=sem_post(&_sem);}
        ~Sem(){int m = sem_destroy(&_sem);}
    private:
        sem_t _sem;
        int _init_vaule;
    };
}




